package com.ffapp.helper.login;

import android.Manifest;
import android.app.AlertDialog;
import android.bluetooth.BluetoothAdapter;
import android.bluetooth.BluetoothDevice;
import android.content.Context;
import android.content.DialogInterface;
import android.content.Intent;
import android.content.pm.PackageManager;
import android.location.LocationManager;
import android.os.Build;
import android.os.Bundle;
import android.provider.Settings;
import android.support.annotation.NonNull;
import android.support.annotation.RequiresApi;
import android.support.v4.app.ActivityCompat;
import android.support.v4.content.ContextCompat;
import android.support.v4.widget.SwipeRefreshLayout;
import android.support.v7.widget.LinearLayoutManager;
import android.support.v7.widget.RecyclerView;
import android.text.TextUtils;
import android.util.Log;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.TextView;

import com.clj.fastble.BleManager;
import com.clj.fastble.callback.BleMtuChangedCallback;
import com.clj.fastble.callback.BleRssiCallback;
import com.clj.fastble.callback.BleScanCallback;
import com.clj.fastble.data.BleDevice;
import com.clj.fastble.exception.BleException;
import com.ffapp.helper.R;
import com.ffapp.helper.basis.BasisActivity;
import com.ffapp.helper.view.MySwipeRefreshLayout;
import com.flyco.dialog.listener.OnBtnClickL;
import com.jcodecraeer.xrecyclerview.ProgressStyle;
import com.jcodecraeer.xrecyclerview.XRecyclerView;
import com.suke.widget.SwitchButton;

import java.util.ArrayList;
import java.util.List;

import butterknife.BindView;
import butterknife.ButterKnife;
import butterknife.OnClick;
import my.DialogUtils;
import my.MySharedPreferences;

public class SearchBlueToothActivity extends BasisActivity {

    BluetoothAdapter bluetoothAdapter = BluetoothAdapter.getDefaultAdapter();
    private static final String TAG = SearchBlueToothActivity.class.getSimpleName();
    private static final int REQUEST_CODE_OPEN_GPS = 1;
    private static final int REQUEST_CODE_PERMISSION_LOCATION = 2;
    private final static int SEARCH_CODE = 0x123;

    private DeviceAdapter mDeviceAdapter;
    private DeviceAdapter mPairDeviceAdapter;

    @BindView(R.id.rv_device)
    XRecyclerView rvDevice;
    @BindView(R.id.rv_pair_device)
    XRecyclerView rvPairDevice;
    @BindView(R.id.switchBtn)
    SwitchButton switchBtn;
    @BindView(R.id.tv_device_name)
    TextView tvDeviceName;
    @BindView(R.id.swipe_refresh_layout)
    MySwipeRefreshLayout swipeRefreshLayout;


    @Override
    public void initViews() {
        setContentView(R.layout.activity_search_blue_tooth);
        mDeviceAdapter = new DeviceAdapter(this);
        LinearLayoutManager layoutManager = new LinearLayoutManager(mContext);
        layoutManager.setOrientation(LinearLayoutManager.VERTICAL);
        rvDevice.setVerticalScrollBarEnabled(true);
        rvDevice.setLayoutManager(layoutManager);
        rvDevice.setRefreshProgressStyle(ProgressStyle.BallSpinFadeLoader);
        rvDevice.setPullRefreshEnabled(false);
        rvDevice.setLoadingMoreEnabled(false);
        rvDevice.setAdapter(mDeviceAdapter);

        mPairDeviceAdapter = new DeviceAdapter(this);
        LinearLayoutManager layoutManagerTwo = new LinearLayoutManager(mContext);
        layoutManager.setOrientation(LinearLayoutManager.VERTICAL);
        rvPairDevice.setVerticalScrollBarEnabled(true);
        rvPairDevice.setLayoutManager(layoutManagerTwo);
        rvPairDevice.setRefreshProgressStyle(ProgressStyle.BallSpinFadeLoader);
        rvPairDevice.setPullRefreshEnabled(false);
        rvPairDevice.setLoadingMoreEnabled(false);
        rvPairDevice.setAdapter(mPairDeviceAdapter);

        swipeRefreshLayout.setEnabled(false);

        switchBtn.setOnCheckedChangeListener(new SwitchButton.OnCheckedChangeListener() {
            @Override
            public void onCheckedChanged(SwitchButton view, boolean isChecked) {
                if (isChecked == true) {
                    blueToothIsOpen();
                    swipeRefreshLayout.setEnabled(true);
                } else {
                    swipeRefreshLayout.setEnabled(false);
//                    BleManager.getInstance().cancelScan();
                    mDeviceAdapter.allClear();
                    mDeviceAdapter.notifyDataSetChanged();
                    mPairDeviceAdapter.allClear();
                    mPairDeviceAdapter.notifyDataSetChanged();
                }
            }
        });

        setTitle("蓝牙");
        setTitleLeftButton(R.drawable.base_icon_back_white, new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                finish();
            }
        });
        tvDeviceName.setText("" + bluetoothAdapter.getName());

        swipeRefreshLayout.setColorSchemeResources(R.color.base_blue, R.color.base_text_green, R.color.base_color_red);
        swipeRefreshLayout.setOnRefreshListener(new SwipeRefreshLayout.OnRefreshListener() {
            @Override
            public void onRefresh() {
                startScan();
            }
        });
    }

    @Override
    protected void onResume() {
        super.onResume();
        showConnectedDevice();
    }

    @Override
    public void initData(Bundle savedInstanceState) {
        setHistoryDeviceZone();
    }

    private void showConnectedDevice() {
        List<BleDevice> deviceList = BleManager.getInstance().getAllConnectedDevice();
        mDeviceAdapter.clearConnectedDevice();
        mPairDeviceAdapter.clearConnectedDevice();
        for (BleDevice bleDevice : deviceList) {
            BluetoothDevice bluetoothDevice = bleDevice.getDevice();
            //没否配对
            if (bluetoothDevice.getBondState() != BluetoothDevice.BOND_BONDED) {
                mDeviceAdapter.addDevice(bleDevice);
            } else {
                mPairDeviceAdapter.addDevice(bleDevice);
            }
        }
        mDeviceAdapter.notifyDataSetChanged();
        mPairDeviceAdapter.notifyDataSetChanged();
    }

    private void startScan() {
        BleManager.getInstance().scan(new BleScanCallback() {
            @Override
            public void onScanStarted(boolean success) {
                mDeviceAdapter.clearScanDevice();
                mDeviceAdapter.notifyDataSetChanged();
                mPairDeviceAdapter.clearScanDevice();
                mPairDeviceAdapter.notifyDataSetChanged();
                swipeRefreshLayout.setRefreshing(true);
                setHistoryDeviceZone();
            }

            @Override
            public void onLeScan(BleDevice bleDevice) {
                super.onLeScan(bleDevice);
            }

            @Override
            public void onScanning(BleDevice bleDevice) {
                BluetoothDevice bluetoothDevice = bleDevice.getDevice();
                //没否配对
                if (bluetoothDevice.getBondState() != BluetoothDevice.BOND_BONDED) {
                    if (isSaveSharePre(bleDevice)) {
                        mPairDeviceAdapter.addDevice(bleDevice);
                        mPairDeviceAdapter.notifyDataSetChanged();
                    } else {
                        mDeviceAdapter.addDevice(bleDevice);
                        mDeviceAdapter.notifyDataSetChanged();
                    }
                } else {
                    mPairDeviceAdapter.addDevice(bleDevice);
                    mPairDeviceAdapter.notifyDataSetChanged();
                }
                setHistoryDeviceZone();
            }

            @Override
            public void onScanFinished(List<BleDevice> scanResultList) {
                swipeRefreshLayout.setRefreshing(false);
            }
        });
    }

    void setHistoryDeviceZone() {
        if (mPairDeviceAdapter != null && mPairDeviceAdapter.getItemCount() > 0) {
            findViewById(R.id.view_history_device_zone).setVisibility(View.VISIBLE);
        } else {
            findViewById(R.id.view_history_device_zone).setVisibility(View.GONE);
        }
    }

    private void readRssi(BleDevice bleDevice) {
        BleManager.getInstance().readRssi(bleDevice, new BleRssiCallback() {
            @Override
            public void onRssiFailure(BleException exception) {
                Log.i(TAG, "onRssiFailure" + exception.toString());
            }

            @Override
            public void onRssiSuccess(int rssi) {
                Log.i(TAG, "onRssiSuccess: " + rssi);
            }
        });
    }

    private void setMtu(BleDevice bleDevice, int mtu) {
        BleManager.getInstance().setMtu(bleDevice, mtu, new BleMtuChangedCallback() {
            @Override
            public void onSetMTUFailure(BleException exception) {
                Log.i(TAG, "onsetMTUFailure" + exception.toString());
            }

            @Override
            public void onMtuChanged(int mtu) {
                Log.i(TAG, "onMtuChanged: " + mtu);
            }
        });
    }

    @Override
    public final void onRequestPermissionsResult(int requestCode,
                                                 @NonNull String[] permissions,
                                                 @NonNull int[] grantResults) {
        super.onRequestPermissionsResult(requestCode, permissions, grantResults);
        switch (requestCode) {
            case REQUEST_CODE_PERMISSION_LOCATION:
                if (grantResults.length > 0) {
                    for (int i = 0; i < grantResults.length; i++) {
                        if (grantResults[i] == PackageManager.PERMISSION_GRANTED) {
                            onPermissionGranted(permissions[i]);
                        }
                    }
                }
                break;
        }
    }

    /**
     * 判断蓝牙是否开启
     */
    private void blueToothIsOpen() {
        BluetoothAdapter bluetoothAdapter = BluetoothAdapter.getDefaultAdapter();
        // 判断手机是否支持蓝牙
        if (bluetoothAdapter == null) {
            showToast("设备不支持蓝牙");
            finish();
        }

        if (!bluetoothAdapter.isEnabled()) {
            //弹出对话框提示用户是后打开
            Intent intent = new Intent(BluetoothAdapter.ACTION_REQUEST_ENABLE);
            startActivityForResult(intent, SEARCH_CODE);
        } else {
//            bluetoothAdapter.enable();         // 不做提示，强行打开
            checkPermissions();   //打开GPS
        }
    }

    private void checkPermissions() {
        String[] permissions = {Manifest.permission.ACCESS_FINE_LOCATION};
        List<String> permissionDeniedList = new ArrayList<>();
        for (String permission : permissions) {
            int permissionCheck = ContextCompat.checkSelfPermission(this, permission);
            if (permissionCheck == PackageManager.PERMISSION_GRANTED) {
                onPermissionGranted(permission);   //如果没点允许手机定位的话     前往设置定位
            } else {
                permissionDeniedList.add(permission);
            }
        }
        if (!permissionDeniedList.isEmpty()) {
            String[] deniedPermissions = permissionDeniedList.toArray(new String[permissionDeniedList.size()]);
            ActivityCompat.requestPermissions(this, deniedPermissions, REQUEST_CODE_PERMISSION_LOCATION);
        }
    }

    private void onPermissionGranted(String permission) {
        switch (permission) {
            case Manifest.permission.ACCESS_FINE_LOCATION:
                if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M && !checkGPSIsOpen()) {
                    DialogUtils.DialogTwo(mContext, "", "当前手机扫描蓝牙需要打开定位功能。", "前往设置", "取消", new OnBtnClickL() {
                        @Override
                        public void onBtnClick() {
                            Intent intent = new Intent(Settings.ACTION_LOCATION_SOURCE_SETTINGS);
                            startActivityForResult(intent, REQUEST_CODE_OPEN_GPS);
                        }
                    }, new OnBtnClickL() {
                        @Override
                        public void onBtnClick() {
                            switchBtn.setChecked(false);
                        }
                    });
                } else {
                    startScan();
                }
                break;
        }
    }

    private boolean checkGPSIsOpen() {
        LocationManager locationManager = (LocationManager) this.getSystemService(Context.LOCATION_SERVICE);
        if (locationManager == null)
            return false;
        return locationManager.isProviderEnabled(LocationManager.GPS_PROVIDER);
    }

    @Override
    protected void onActivityResult(int requestCode, int resultCode, Intent data) {
        super.onActivityResult(requestCode, resultCode, data);
        if (requestCode == REQUEST_CODE_OPEN_GPS) {
            if (checkGPSIsOpen()) {
                swipeRefreshLayout.setEnabled(true);
                startScan();
            }
        }
        if (requestCode == SEARCH_CODE) {
            switch (resultCode) {
                case RESULT_OK:
                    checkPermissions();
                    break;
                case RESULT_CANCELED:
                    switchBtn.setChecked(false);
                    break;
            }
        }
    }

    private final int REQUEST_SERVER_CHOOSE = 14;

    public class DeviceAdapter extends RecyclerView.Adapter<DeviceAdapter.ViewHolder> {
        private Context context;
        private List<BleDevice> bleDeviceList;

        public DeviceAdapter(Context context) {
            this.context = context;
            bleDeviceList = new ArrayList<>();
        }

        public void addDevice(BleDevice bleDevice) {
            removeDevice(bleDevice);
            bleDeviceList.add(bleDevice);
        }

        public void removeDevice(BleDevice bleDevice) {
            for (int i = 0; i < bleDeviceList.size(); i++) {
                BleDevice device = bleDeviceList.get(i);
                if (bleDevice.getKey().equals(device.getKey())) {
                    bleDeviceList.remove(i);
                }
            }
        }

        public void clearConnectedDevice() {
            for (int i = 0; i < bleDeviceList.size(); i++) {
                BleDevice device = bleDeviceList.get(i);
                if (BleManager.getInstance().isConnected(device)) {
                    bleDeviceList.remove(i);
                }
            }
        }

        public void clearScanDevice() {
            for (int i = 0; i < bleDeviceList.size(); i++) {
                BleDevice device = bleDeviceList.get(i);
                if (!BleManager.getInstance().isConnected(device)) {
                    bleDeviceList.remove(i);
                }
            }
        }

        public void clear() {
            clearConnectedDevice();
            clearScanDevice();
        }

        public void allClear() {
            bleDeviceList.removeAll(bleDeviceList);
        }

        //创建新View，被LayoutManager所调用
        @Override
        public ViewHolder onCreateViewHolder(ViewGroup viewGroup, int viewType) {
            View view = LayoutInflater.from(viewGroup.getContext()).inflate(R.layout.search_blue_tooth_list_item, viewGroup, false);
            return new ViewHolder(view);
        }

        //将数据与界面进行绑定的操作
        @RequiresApi(api = Build.VERSION_CODES.JELLY_BEAN_MR2)
        @Override
        public void onBindViewHolder(ViewHolder viewHolder, int position) {
            viewHolder.bind(position);
        }

        @Override
        public int getItemCount() {
            return bleDeviceList == null ? 0 : bleDeviceList.size();
        }

        //自定义的ViewHolder，持有每个Item的的所有界面元素
        public class ViewHolder extends RecyclerView.ViewHolder {
            @BindView(R.id.list_item)
            public View list_item;
            @BindView(R.id.text_name)
            public TextView device_name;
            @BindView(R.id.text_address)
            public TextView device_address;

            public ViewHolder(View view) {
                super(view);
                ButterKnife.bind(this, view);
            }

            @RequiresApi(api = Build.VERSION_CODES.JELLY_BEAN_MR2)
            public void bind(int position) {
                BleDevice bleDevice = bleDeviceList.get(position);
                //设备名称
                String deviceName = bleDevice.getDevice().getName();
                device_name.setText(TextUtils.isEmpty(deviceName) ? "未知设备" : deviceName);
                String deviceAddress = bleDevice.getDevice().getAddress();
                device_address.setText("" + deviceAddress);
                list_item.setTag(bleDevice);
            }

            @OnClick(R.id.list_item)
            public void onItemClick(View v) {
                BleDevice bleDevice = (BleDevice) v.getTag();
                Bundle extras = new Bundle();
                extras.putParcelable("bleDevice", bleDevice);
                Intent intent = new Intent();
                intent.setClass(context, LoginActivity.class);
                intent.putExtras(extras);
                setResult(REQUEST_SERVER_CHOOSE, intent);
                finish();
            }
        }
    }

    private boolean isSaveSharePre(BleDevice bleDevice) {
        MySharedPreferences mSp = new MySharedPreferences(this);
        if (TextUtils.isEmpty(mSp.getString(bleDevice.getDevice().getAddress()))) {
            return false;
        } else {
            return true;
        }
    }

}
